﻿// CPopAccount.cpp: 实现文件
//

#include "pch.h"
#include "DntDemo.h"
#include "afxdialogex.h"
#include "CPopAccount.h"

#include "DntTest.h"

#define CPP CPopAccount::
#define TAG	"PopAccount"


////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// 标准C语言函数 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

void CPP setLineText(int position, int sub, char* row) {
	if (row != NULL) {
		CString text1(row);
		mList1.SetItemText(position, sub, text1);
	}
	else {
		mList1.SetItemText(position, sub, L"");
	}
}

void CPP ShowLine(int position, char* row1, char* row2) {				// 显示每行的数据
	//CLOGI(TAG, "列表账号SSS (%d)(%s)(%s)", position, row1, row2);
	if (position >= gLine) {
		mList1.InsertItem(position, L"", 0);
		gLine = position + 1;
		CString text;
		text.Format(L"%d", gLine);
		mList1.SetItemText(position, 0, text);	// 第一列
	}
	setLineText(position, 1, row1);				// 第二列
	setLineText(position, 2, row2);				// 第三列
}

void CPP DispList() {													// 列表显示
	int position = 0;
	mList1.DeleteAllItems();
	gLine = 0;
	int conter = 0;					// 列表中真实有效的序列

	char listacc[128];
	char listcode[128];
	char listname[128];
	char listpsw[128];

	for (int index = 0; index < 100; index++) {
		TxtFormat(listacc, sizeof(listacc), "Dvc_%d", index);
		DbsGetMemText(listname, sizeof(listname), listacc);				// 读取列表的账号

		TxtFormat(listcode, sizeof(listcode), "Psw_%d", index);
		DbsGetMemText(listpsw, sizeof(listpsw), listcode);				// 读取列表的访问码

		if (strlen(listname) > 0) {			// 查看账号是否有效
			gRecord[conter] = index;		// 最大100个，记忆列表的位置，为了删除使用
			//CLOGI(TAG, "列表账号TTT (%d)(%d)(%d)", index, gRecord[conter], conter);
			ShowLine(conter++, listname, listpsw);		
		}
	}
}


////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// C++语言对话框函数 ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

// CPopAccount 对话框

IMPLEMENT_DYNAMIC(CPopAccount, CDialogEx)

CPopAccount::CPopAccount(CWnd* pParent /*=nullptr*/)
	: CDialogEx(IDD_POP_ACCOUNT, pParent){
}

CPopAccount::~CPopAccount(){			// 退出页面
	PlatformSetUiCallback(NULL);		// UI回调函数
}

void CPopAccount::DoDataExchange(CDataExchange* pDX){
	CDialogEx::DoDataExchange(pDX);
	DDX_Control(pDX, IDC_LIST1, mList1);
}

BEGIN_MESSAGE_MAP(CPopAccount, CDialogEx)
	ON_WM_TIMER()
	ON_BN_CLICKED(IDC_BUTTON_LOGIN, &CPopAccount::OnBnClickedButtonLogin)
	ON_BN_CLICKED(IDC_BUTTON_DELATE, &CPopAccount::OnBnClickedButtonDelate)
	ON_BN_CLICKED(IDC_BUTTON_DEVICE_LOGIN, &CPopAccount::OnBnClickedButtonDeviceLogin)
	ON_NOTIFY(NM_DBLCLK, IDC_LIST1, &CPopAccount::OnDblclkList1)
END_MESSAGE_MAP()

CPopAccount* mCPopAccount = NULL;
void uiCallback(int bit, DNT_RUN_BIT errorBit, DNT_ERROR errorType) {		// UI回调函数
	//CLOGI(TAG, "回调参数WW  (%d)", mCPopAccount);
	if (mCPopAccount != NULL) {
		mCPopAccount->ShowRegister(bit, errorBit, errorType);
	}
}

BOOL CPopAccount::OnInitDialog() {
	CDialogEx::OnInitDialog();
	// TODO:  在此添加额外的初始化
	mList1.SetExtendedStyle(LVS_EX_FULLROWSELECT | LVS_EX_SUBITEMIMAGES | LVS_EX_HEADERDRAGDROP | LVS_EX_MULTIWORKAREAS);
	int col = 0;

	mList1.InsertColumn(col++, _T("昵称"), LVCFMT_LEFT, 130);
	mList1.InsertColumn(col++, L"设备账号列表", LVCFMT_LEFT, 180);
	mList1.InsertColumn(col++, L"访问码", LVCFMT_LEFT, 120);

	gClick = 0;
	DispList();								// 列表显示
	PlatformSetUiCallback(uiCallback);		// UI回调函数
	mCPopAccount = this;
	ShowAccount(true);
	SetTimer(1, 1000, NULL);
	return TRUE;  // return TRUE unless you set the focus to a control
	// 异常: OCX 属性页应返回 FALSE
}

void CPopAccount::ShowRegister(int bit, DNT_RUN_BIT errorBit, DNT_ERROR errorType) {
	//CLOGI(TAG, "回调参数TTT  (%04x) type(%d) bit(%04x) (%d)", bit, errorType, errorBit, gClick);
	if (gClick == 1) {					// 首次点击登录账号时
		if (bit == DNT_BIT_OK_LOGIN || bit == DNT_BIT_NEED_JOIN_G) {			// 账号登录成功(0x0004)
			((CStatic*)GetDlgItem(IDC_LOGIN_STATE_ACC))->SetWindowText(L"账号状态：已登录");
		}
	}
	else {
		if (bit == DNT_BIT_OK_LOGIN || bit == DNT_BIT_NEED_JOIN_G) {			// 账号登录成功(0x0004)
			((CStatic*)GetDlgItem(IDC_LOGIN_STATE_ACC))->SetWindowText(L"账号状态：已登录");
		}

		if (bit == DNT_BIT_OK_JOIN_G) {											// 设备连接成功(0x0020)
			((CStatic*)GetDlgItem(IDC_LOGIN_STATE_DEVICE))->SetWindowText(L"设备状态：已连接");
			char device[128];
			char code[128];
			DbsGetMemText(device, sizeof(device), "temp_dvc");
			DbsGetMemText(code, sizeof(code), "temp_psw");
			SaveDevice(device, code);											// 写入设备账号到DntDemo.ini
			DispList();															// 列表显示
		}
	}

	if (bit == DNT_BIT_SVR_ERROR) {						// 服务器返回出错(0x4000)
		if (errorBit == DNT_RB_LOGIN) {					// 账号登录出错(0x04)
			if (errorType == DNT_ERR_NAME) {			// 账号名出错(4)
				((CStatic*)GetDlgItem(IDC_LOGIN_STATE_ACC))->SetWindowText(L"账号状态：账号出错");
			}
			else if (errorType == DNT_ERR_PSW) {		// 账号密码出错(5)
				((CStatic*)GetDlgItem(IDC_LOGIN_STATE_ACC))->SetWindowText(L"账号状态：密码出错");
			}
		}

		if (errorBit == DNT_RB_JOIN_GROUP) {			// 设备连接出错(0x08)
			/*
			// 测试添加到列表的数据
			char device[128];
			char code[128];
			DbsGetMemText(device, sizeof(device), "temp_dvc");
			DbsGetMemText(code, sizeof(code), "temp_psw");
			SaveDevice(device, code);											// 写入设备账号到DntDemo.ini
			DispList();															// 列表显示
			*/
			if (errorType == DNT_ERR_DN) {				// 电器设备账号名出错(6)
				((CStatic*)GetDlgItem(IDC_LOGIN_STATE_DEVICE))->SetWindowText(L"设备状态：设备出错");
			}
			else if (errorType == DNT_ERR_VISIT) {		// 账号访问码出错(7)
				((CStatic*)GetDlgItem(IDC_LOGIN_STATE_DEVICE))->SetWindowText(L"设备状态：访问码出错");
			}
		}
	}

	if (bit == DNT_BIT_TIMEOUT) {
		((CStatic*)GetDlgItem(IDC_LOGIN_STATE_ACC))->SetWindowText(L"账号状态：连接超时");
		((CStatic*)GetDlgItem(IDC_LOGIN_STATE_DEVICE))->SetWindowText(L"设备状态：连接超时");
	}
}

void CPopAccount::OnTimer(UINT_PTR nIDEvent) {
	// TODO: 在此添加消息处理程序代码和/或调用默认值
	CDialogEx::OnTimer(nIDEvent);
}

// CPopAccount 消息处理程序
////////////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////////////
void CPopAccount::ShowAccount(bool init) {			// 账号信息
	char bytes[100];
	char an_0[32];
	DbsGetMemText(an_0, sizeof(an_0), "an_0");
	TxtFormat(bytes, sizeof(bytes), "%s", an_0);
	CString text(bytes);
	((CEdit*)GetDlgItem(IDC_EDIT_NAME))->SetWindowText(text);

	char bytesA[100];
	char ap_0[32];
	DbsGetMemText(ap_0, sizeof(ap_0), "ap_0");
	TxtFormat(bytesA, sizeof(bytesA), "%s", ap_0);
	CString textA(bytesA);
	((CEdit*)GetDlgItem(IDC_EDIT_PSW))->SetWindowText(textA);

	char bytesB[100];
	char an_1[32];
	DbsGetMemText(an_1, sizeof(an_1), "an_1");
	TxtFormat(bytesB, sizeof(bytesB), "%s",an_1);
	CString textB(bytesB);
	((CEdit*)GetDlgItem(IDC_EDIT_DEVICE_NAME))->SetWindowText(textB);

	char bytesC[100];
	char gv_1[32];
	DbsGetMemText(gv_1, sizeof(gv_1), "gv_1");
	TxtFormat(bytesC, sizeof(bytesC), "%s", gv_1);
	CString textC(bytesC);
	((CEdit*)GetDlgItem(IDC_EDIT_ACCESS_CODE))->SetWindowText(textC);
}

void CPopAccount::OnBnClickedButtonLogin(){		// 登录用户账号
	gClick++;
	char bytes[128];
	CString string;
	((CEdit*)GetDlgItem(IDC_EDIT_NAME))->GetWindowText(string);
	TxtUnicodeUtf8(bytes, sizeof(bytes), (short*)string.AllocSysString());	// UNICODE转换到GUTF8
	DbsSetMemText("an_0", bytes);
	((CEdit*)GetDlgItem(IDC_EDIT_PSW))->GetWindowText(string);
	TxtUnicodeUtf8(bytes, sizeof(bytes), (short*)string.AllocSysString());	// UNICODE转换到GUTF8
	DbsSetMemText("ap_0", bytes);

	if (DbsGetMemText(bytes, sizeof(bytes), "an_0") > 0) {					// 账号不是空
		if (DbsGetMemText(bytes, sizeof(bytes), "ap_0") > 0) {				// 密码不是空
			DntSetIdleFlag(DNT_RB_LOGIN);
			return;
		}
		::AfxMessageBox(L"请输入动态域名的账号密码");
		return;
	}
	::AfxMessageBox(L"请输入动态域名的账号名");
}

void CPopAccount::OnBnClickedButtonDelate(){	// 删除账号
	int nItem = mList1.GetSelectionMark();		// 获取选中行的编号
	CLOGI(TAG, "删除账号TTT (%d)(%d)", nItem, gRecord[nItem]);
	char dvc[16];
	TxtFormat(dvc, sizeof(dvc), "Dvc_%d", gRecord[nItem]);
	char psw[16];
	TxtFormat(psw, sizeof(psw), "Psw_%d", gRecord[nItem]);
	DbsSetMemText(dvc, NULL);								// 写入NULL到memory.ini中，NULL是表示删除
	DbsSetMemText(psw, NULL);								// 写入NULL到memory.ini中，NULL是表示删除
	DispList();												// 列表显示
}

void CPopAccount::OnDblclkList1(NMHDR* pNMHDR, LRESULT* pResult) {	// 双击选择账号
	int nItem = mList1.GetSelectionMark();							// 获取选中行的编号
	CString name = mList1.GetItemText(nItem, 1);					// 选中的行、列的值（1为第一列）
	((CEdit*)GetDlgItem(IDC_EDIT_DEVICE_NAME))->SetWindowText(name);// 插入到编辑框中显示
	CString code = mList1.GetItemText(nItem, 2);					// 选中的行、列的值（2为第二列）
	((CEdit*)GetDlgItem(IDC_EDIT_ACCESS_CODE))->SetWindowText(code);// 插入到编辑框中显示
}

void CPP SaveDevice(char* device, char* code) {				// 写入设备账号到DntDemo.ini
	char listacc[16];
	int position = -1;										// 列表中数据的位置
	char listname[128];
	int textlength = (int)strlen(device);					// 账号的长度
	int index = 0;
	for (; index < 100; index++) {
		TxtFormat(listacc, sizeof(listacc), "Dvc_%d", index);
		DbsGetMemText(listname, sizeof(listname), listacc);
		if (strlen(listname) == 0) {						// 查看账号是否有效，等于0表示无效数据
			if (position == -1){
				position = index;							// 无效数据的位置
			}
		}
		if (!memcmp(device, listname, textlength)) {		// 列表中有相同的数据
			position = index;								// 有效数据的位置
			break;
		}
	}
	if (position == -1) {
		position = index;
	}

	char dvc[16];
	TxtFormat(dvc, sizeof(dvc), "Dvc_%d", position);
	char psw[16];
	TxtFormat(psw, sizeof(psw), "Psw_%d", position);
	DbsSetMemText(dvc, device);		// 写入memory.ini 的字符串键值对 文字
	DbsSetMemText(psw, code);		// 写入memory.ini 的字符串键值对 文字
}


void CPopAccount::OnBnClickedButtonDeviceLogin(){	// 连接设备账号
	gClick = gClick + 2;
	char device[128];
	char code[128];
	CString string;

	((CEdit*)GetDlgItem(IDC_EDIT_DEVICE_NAME))->GetWindowText(string);
	TxtUnicodeUtf8(device, sizeof(device), (short*)string.AllocSysString());	// UNICODE转换到GUTF8
	DbsSetMemText("temp_dvc", device);
	DbsSetMemText("an_1", device);
	((CEdit*)GetDlgItem(IDC_EDIT_ACCESS_CODE))->GetWindowText(string);
	TxtUnicodeUtf8(code, sizeof(code), (short*)string.AllocSysString());		// UNICODE转换到GUTF8
	DbsSetMemText("temp_psw", code);
	DbsSetMemText("gv_1", code);

	if (DbsGetMemText(device, sizeof(device), "temp_dvc") > 0) {				// 账号不为空
		if (DbsGetMemText(code, sizeof(code), "temp_psw") > 0) {				// 密码不为空
			DntSetIdleFlag(DNT_RB_JOIN_GROUP);
			return;
		}
		::AfxMessageBox(L"请输入电器设备端的账号密码");
		return;
	}
	::AfxMessageBox(L"请输入电器设备端的账号名");
}